package com.fantsey.test.juejin;

import java.util.Comparator;
import java.util.HashMap;
import java.util.HashSet;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.stream.Collectors;
import java.util.stream.Stream;

/**
 * 德州扑克是一种经典的扑克游戏，里面有一种牌型叫“葫芦”。
 * “葫芦”由五张牌组成，其中包含三张一样的牌a和另外两张一样的牌b。
 * “葫芦”跟“葫芦”之间可以比较大小，先比较a的大小，如果a一样大再比较b的大小。
 * 德州扑克不包含大小王，只包含常规的52张牌。在13种不同的牌面里面，大小规则是A > K > Q > J > 10 > 9 > ... > 2。也就是说，A最大，K次之，2最小。
 * 这里给“葫芦”加一个限制规则，“葫芦”的牌面值之和不能超过max（可以等于），A，2，3，...，J，Q，K的牌面值分别是1到13。
 *
 * 给出n张牌，从里面寻找符合规则的最大葫芦组合
 *
 * 最大的葫芦组合里面，三张的牌面和两张的牌面，如果没有葫芦则输出“0，0”
 *
 * 输入样式
 * 样例1
 * 9 34
 * 6 6 6 8 8 8 5 5 1       ------------> 888 55 24+10=34<=34
 * 样例2
 * 9 37
 * 9 9 9 9 6 6 6 6 13      ------------ 666 99  18+18=36<37
 * 样例3
 * 9 40
 * 1 11 13 12 7 8 11 5 6   ----------- 0,0
 *
 * 样例1
 * 8 5
 *
 * 样例2
 * 6 9
 *
 * 样例3
 * 0 0
 *
 * 数据范围
 * 牌数n的范围：5 < n < 40，0 < max < 100
 * 牌面的范围：1 ≤ v ≤ 13
 * 跟现实中扑克一样，每种牌面最多4张
 *
 * @author fx
 * @date 2024/12/26
 * @since 1.0
 */
public class Question5 {

    /**
     * 1. 先分别找出a的数值，及3个一样大的牌，并按大到小排列
     * 2. 再找出b牌（除去a牌剩下的），即2个一样大的牌，按大到小排列
     *      - 如果a牌有2个以上，则取其中一个当b牌， 计算其和是否超过max, 如果超过则取下一个
     *      - 如果a牌只有1个，则取b牌， 计算其和是否超过max, 如果超过则取下一个
     *      - 如果a牌没有，则返回0,0
     *
     *  ps:
     *  1. 注意a>k , 即1点是最大的，其次是1>13>12>....>2
     *  2. 优先选a大的组合
     */
    public static int[] solution(int n, int max, int[] array) {
        // Edit your code here
        Map<Integer, Integer> numberCountMap = new HashMap<>(16);
        for (int i=0; i<array.length; i++) {
            if (numberCountMap.containsKey(array[i])) {
                numberCountMap.put(array[i], numberCountMap.get(array[i]) + 1);
            } else {
                numberCountMap.put(array[i], 1);
            }
        }
        int[] emptyResult = new int[]{0, 0};
        Set<Integer> aNumberSet = new HashSet<>();
        Set<Integer> bNumberSet = new HashSet<>();
        for (Map.Entry<Integer,Integer> entry : numberCountMap.entrySet()) {
            int key = entry.getKey();
            int value = entry.getValue();
            if (value >= 3) {
                aNumberSet.add(key);
            }
            if (value >= 2) {
                bNumberSet.add(key);
            }
        }

        if (aNumberSet.isEmpty() || bNumberSet.isEmpty()) {
            return emptyResult;
        }

        Comparator<Integer> comparator = (o1, o2) -> {
            if (o1 == 1) {
                return -1;
            }
            if (o2 == 1) {
                return 1;
            }
            return o2 - o1;
        };
        List<Integer> sortedANumberList = aNumberSet.stream().sorted(comparator).collect(Collectors.toList());
        List<Integer> sortedBNumberList = bNumberSet.stream().sorted(comparator).collect(Collectors.toList());
        Map<Integer, List<Integer>> suitableResultMap = new LinkedHashMap<>();
        for (int aNumberValue : sortedANumberList) {
            int sumA = aNumberValue * 3;
            // 如果a牌值为1， 即牌A，为最大的组合，此时只需要考虑后续的b牌，不用在遍历其他a牌
            for (int bNumberValue : sortedBNumberList) {
                int sumB = bNumberValue * 2;
                // 如果两个相等，说明b牌是a牌,跳过
                if (aNumberValue == bNumberValue) {
                    continue;
                }
                int totalSum = sumA + sumB;
                // 如果b牌有1，则也跟a牌类似，不用遍历剩下的
                if (aNumberValue == 1 || bNumberValue==1) {
                    if (totalSum > max) {
                        continue;
                    }
                    return new int[]{aNumberValue, bNumberValue};
                }
                if (totalSum > max) {
                    continue;
                }

                // a牌排序后，只保留b牌最大的
                if (suitableResultMap.containsKey(aNumberValue)) {
                    List<Integer> list = suitableResultMap.get(aNumberValue);
                    if (list.get(1) < bNumberValue) {
                        suitableResultMap.put(aNumberValue, Stream.of(aNumberValue, bNumberValue).collect(Collectors.toList()));
                    }
                } else {
                    suitableResultMap.put(aNumberValue, Stream.of(aNumberValue, bNumberValue).collect(Collectors.toList()));
                }
            }

        }
        if (suitableResultMap.isEmpty()) {
            return emptyResult;
        }

        List<Integer> resultList = suitableResultMap.entrySet().iterator().next().getValue();
        System.out.println("resultList:" + resultList);

        return new int[]{resultList.get(0), resultList.get(1)};
    }

    public static void main(String[] args) {
        // Add your test cases here

        /*System.out.println(java.util.Arrays.equals(solution(9, 34, new int[]{6, 6, 6, 8, 8, 8, 5, 5, 1}), new int[]{8, 5}));
        System.out.println(java.util.Arrays.equals(solution(9, 37, new int[]{9, 9, 9, 9, 6, 6, 6, 6, 13}), new int[]{6, 9}));
        System.out.println(java.util.Arrays.equals(solution(9, 40, new int[]{1, 11, 13, 12, 7, 8, 11, 5, 6}), new int[]{0, 0}));

        System.out.println(solution(31, 42, new int[]{3,3,11,12,12,2,13,5,13,1,13,8,8,1,8,13,12,9,2,11,3,5,8,11,1,11,1,5,4,2,5})[0] + "," + solution(31, 42, new int[]{3,3,11,12,12,2,13,5,13,1,13,8,8,1,8,13,12,9,2,11,3,5,8,11,1,11,1,5,4,2,5})[1]);

        System.out.println(java.util.Arrays.equals(solution(31, 42, new int[]{3,3,11,12,12,2,13,5,13,1,13,8,8,1,8,13,12,9,2,11,3,5,8,11,1,11,1,5,4,2,5}), new int[]{1, 13}));*/


        //System.out.println(java.util.Arrays.equals(solution(25, 8, new int[]{10,13,9,5,12,10,13,7,1,2,13,3,7,1,5,10,1,5,7,1,7,8,13,10,5}), new int[]{0, 0}));

        //System.out.println(java.util.Arrays.equals(solution(9, 34, new int[]{6,6,6,8,8,8,5,5,1}), new int[]{8, 5}));

        System.out.println(java.util.Arrays.equals(solution(28, 104, new int[]{2,6,12,2,8,12,12,7,10,4,11,8,6,2,3,12,9,8,6,6,3,10,10,9,3,10,2,8}), new int[]{12, 10}));

    }

}
